#pragma once

#include <properties/Command.h>
#include <Atom.h>
#include <map>
#include <WowPtr.h>
#include <boost/noncopyable.hpp>

namespace liba {
namespace properties {

class CommandContainer
	: public virtual WowPointable
	, private boost::noncopyable
{
public:
	AbstractCommand* FindAbstractCommand(const Atom& name);

	Command<>* FindCommand(const Atom& name) { return FindCommandInternal<Command<> >(name); }

	template<typename T1>
	Command<T1>* FindCommand(const Atom& name) { return FindCommandInternal<Command<T1> >(name); }

	void RegisterCommand(const Atom& name, AbstractCommand* cmd);
private:
	template<typename CmdType>
	CmdType* FindCommandInternal(const Atom& name) 
	{
		AbstractCommand* ac = FindAbstractCommand(name);
		if (!ac)
			return 0;
		return dynamic_cast<CmdType*>(ac);
	}

	typedef std::map<Atom, AbstractCommand*> Commands;
	Commands commands;
};

} // namespace properties
} // namespace liba